﻿using MongoDB.Driver;
using Sustainalytics.ClientDW.Entities;
using Sustainalytics.Entities.RiskRatings;
using Sustainalytics.ESG.Entities;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Sustainalytics.ScreeningTool.Synchronization.Handlers.ESG
{
    public class RPControversyIndicatorHandler : IHandlerWithGrouping<RPControversyIndicator>
    {
        public ProjectionDefinition<RPControversyIndicator> GetProjection(ProjectionDefinitionBuilder<RPControversyIndicator> builder) => builder
            .Include(x => x.AnswerCategory)
            .Include(x => x.AnswerCategoryScore)
            .Include(x => x.AnswerCategoryText)
            .Include(x => x.Template.Number)
            .Include(x => x.Template.Name)
            .Include(x => x.OutlookScore)
            .Include(x => x.EventIndicators);

        public IEnumerable<ExtraElement> GetExtraElements(IEnumerable<RPControversyIndicator> entities)
        {
            var highestControversyLevel = entities.Max(x => x.AnswerCategory);
            var highestControversyIndicatorList = entities.Where(x => x.AnswerCategory == highestControversyLevel).Select(x => x);
            var highestControversyLevelOutlookScore = 1;

            List<ExtraElement> extraElements = new List<ExtraElement>();
            StringBuilder highestControversyIndicatorName = new StringBuilder();

            foreach (RPControversyIndicator indicator in highestControversyIndicatorList)
            {
                if (indicator.OutlookScore != highestControversyLevelOutlookScore)
                {
                    if (indicator.OutlookScore == -1)
                        highestControversyLevelOutlookScore = -1;
                    else if (indicator.OutlookScore == 0 && highestControversyLevelOutlookScore != -1)
                        highestControversyLevelOutlookScore = 0;
                }

                var key = $"{indicator.Template.Number} {indicator.Template.Name}";
                extraElements.Add(new ExtraElement($"{key}-Category", ((RiskRatingClusterAssessment)indicator.AnswerCategory).ToString()));
                highestControversyIndicatorName.Append(indicator.Template.Name).Append("; ");
            }

            extraElements.AddRange(new ExtraElementList
            {
                { "Highest Controversy Level-Outlook Score",highestControversyLevelOutlookScore},
                { "Highest Controversy Level-Category",((RiskRatingClusterAssessment)highestControversyLevel).ToString()},
                { "Highest Controversy Level-Controversy Name", highestControversyIndicatorName.ToString()},
            });

            return entities.SelectMany(x =>
            {
                var key = $"{x.Template.Number} {x.Template.Name}";
                return new ExtraElementList
                {
                    { $"{key}-Answer Category",      x.AnswerCategory      },
                    { $"{key}-Answer Category text", x.AnswerCategoryText  },
                    { $"{key}-Raw Score",            x.AnswerCategoryScore },
                };
            })
            .Concat(new[] { new ExtraElement("Highest Controversy Level-Answer Category", highestControversyLevel) })
            .Concat(extraElements);
        }
    }
}
